package model

import (
	"github.com/lab-online/internal/course/entity"
	"github.com/lab-online/pkg/model"
	"github.com/lab-online/pkg/util"
)

type Course struct {
	model.BaseModel
	Name        string       `gorm:"type:varchar(100);not null"`
	Description string       `gorm:"type:varchar(256)"`
	Experiments []Experiment `gorm:"many2many:course_experiments;"`
}

func (c *Course) ToEntity(courseExperiments []CourseExperiment) entity.CourseEntity {
	return entity.NewCourseEntity(func(e *entity.Course) {
		e.ID = c.ID
		e.Name = c.Name
		e.Description = c.Description
		e.CourseExperimentMeta = util.SliceMap(courseExperiments,
			func(courseExperiment CourseExperiment) entity.CourseExperiment {
				return entity.CourseExperiment{
					ExperimentID: courseExperiment.ExperimentID,
					Index:        courseExperiment.Index,
					Meta:         courseExperiment.Meta,
				}
			},
		)
		e.Experiments = util.SliceMap(c.Experiments,
			func(experiment Experiment) entity.Experiment {
				exp := entity.Experiment{
					Name:        experiment.Name,
					Queue:       experiment.Queue,
					Description: experiment.Description,
				}
				exp.ID = experiment.ID

				return exp
			})
	})
}

type CourseOption func(*Course)

func NewCourse(options ...CourseOption) *Course {
	c := &Course{}
	for _, option := range options {
		option(c)
	}
	return c
}

func WithCourseID(id uint) CourseOption {
	return func(c *Course) {
		c.ID = id
	}
}

func WithCourseEntity(e entity.CourseEntity) CourseOption {
	return func(c *Course) {
		c.ID = e.GetID()
		c.Name = e.GetName()
		c.Description = e.GetDescription()
	}
}
